import axios, { AxiosInstance } from 'axios'
import { getAuthToken } from '@/localStorage/index'


/**
 * 将object拼接成为a=b&c=d……的字符串
 * @param  {*} params 
 * @return 
 */
function queryParams(params: any) {
  if (!params) return ''
  return Object.keys(params)
    .map(k => {
      const value = params[k]
      const noValue = !value && value !== 0
      return `${k}=${noValue ? '' : value}`
    })
    .join('&')
}

class axiosService {
  baseUrl: string = ''
  instance: AxiosInstance
  
  constructor() {
    const instance = axios.create()
    
    instance.interceptors.request.use(
      async (config) => {
        const accessToken = await getAuthToken()
        // @ts-ignore
        config.headers = {
          UserToken: accessToken || '',
        }
        return config
      },
      (error) => {
        Promise.reject(error)
      },
    )
    
    instance.interceptors.response.use(
      (response) => {
        // @ts-ignore
        response.duration = new Date().getTime()
        const errMsg = response.headers.error || response.headers.Error
        if (response.status === 200) {
          if (!errMsg) {
            return response.data.data
          }
          return Promise.reject(response.data)
        }
        return Promise.reject(new Error(`The server is not available. Try connecting this device again. code: ${response.status}`))
      },
      async (error) => {
        const originalRequest = error.config
        console.log(error)
        return Promise.reject(error)
      },
    )
    this.instance = instance
  }
  
  setBaseUrl(baseUrl: string) {
    this.baseUrl = baseUrl
  }
  
  get<T>(url: string, data?: any): Promise<T> {
    let curUrl = url
    if (data) {
      curUrl = url + '?' + queryParams(data)
    }
    console.log('CALL URL', `${this.baseUrl}${curUrl}`)
    return this.instance.get(`${this.baseUrl}${curUrl}`) as Promise<T>
  }
  
  post<T>(url: string, body: any) {
    return this.instance.post(`${this.baseUrl}${url}`, body)  as Promise<T>
  }
  
  patch<T>(url: string, body: any) {
    return this.instance.patch(`${this.baseUrl}${url}`, body)  as Promise<T>
  }
  
  delete(url: string) {
    return this.instance.delete(`${this.baseUrl}${url}`)
  }
}

export default new axiosService()
